<?php

class Link_Plugin_Parser implements Iterator
{

	/**
	 * Holds all the Open Graph values we've parsed from a page
	 *
	 */
	protected $_values = array();

	/**
	 * Parses HTML and extracts Open Graph data, this assumes
	 * the document is at least well formed.
	 *
	 * @param $HTML    HTML to parse
	 * @return OpenGraph
	 */
	static public function parse($HTML)
	{
		$old_libxml_error = libxml_use_internal_errors(true);

		$doc = new DOMDocument();
		$doc -> loadHTML($HTML);

		libxml_use_internal_errors($old_libxml_error);

		$tags = $doc -> getElementsByTagName('meta');
		
		if (!$tags || $tags -> length === 0)
		{
			return false;
		}

		$page = new self();

		foreach ($tags AS $tag)
		{
			if ($tag -> hasAttribute('property') && strpos($tag -> getAttribute('property'), 'og:') === 0)
			{
				$key = strtr(substr($tag -> getAttribute('property'), 3), '-', '_');
				$page -> _values[$key] = $tag -> getAttribute('content');
			}
		}

		if (empty($page -> _values))
		{
			return false;
		}

		return $page;
	}

	/**
	 * Helper method to access attributes directly
	 * Example:
	 * $graph->title
	 *
	 * @param $key    Key to fetch from the lookup
	 */
	public function __get($key)
	{
		if (array_key_exists($key, $this -> _values))
		{
			return $this -> _values[$key];
		}
	}

	/**
	 * Return all the keys found on the page
	 *
	 * @return array
	 */
	public function keys()
	{
		return array_keys($this -> _values);
	}

	/**
	 * Helper method to check an attribute exists
	 *
	 * @param $key
	 */
	public function __isset($key)
	{
		return array_key_exists($key, $this -> _values);
	}

	/**
	 * Will return true if the page has location data embedded
	 *
	 * @return boolean Check if the page has location data
	 */
	public function hasLocation()
	{
		if (array_key_exists('latitude', $this -> _values) && array_key_exists('longitude', $this -> _values))
		{
			return true;
		}

		$address_keys = array(
			'street_address',
			'locality',
			'region',
			'postal_code',
			'country_name'
		);

		$valid_address = true;

		foreach ($address_keys AS $key)
		{
			$valid_address = ($valid_address && array_key_exists($key, $this -> _values));
		}
		return $valid_address;
	}

	/**
	 * Iterator code
	 */
	private $_position = 0;

	public function rewind()
	{
		reset($this -> _values);
		$this -> _position = 0;
	}

	public function current()
	{
		return current($this -> _values);
	}

	public function key()
	{
		return key($this -> _values);
	}

	public function next()
	{
		next($this -> _values);
		++$this -> _position;
	}

	public function valid()
	{
		return $this -> _position < sizeof($this -> _values);
	}

}
